package com.shengde.jinwawaforleader.utils;

import android.content.Context;
import android.content.res.Resources;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.PixelFormat;
import android.graphics.Rect;
import android.graphics.drawable.Drawable;
import android.util.Base64;

import com.shengde.jinwawaforleader.R;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.lang.ref.WeakReference;
import java.net.HttpURLConnection;
import java.net.URL;

/**
 * 15.8.12 压缩图片 1. 使用inJustDecodeBounds，仅仅读bitmap的长和宽。 2.
 * 根据bitmap的长款和目标缩略图的长和宽，计算出inSampleSize的大小。 3.
 * 使用inSampleSize，载入一个比imageview大一点的缩略图A 4.
 * 使用createScaseBitmap再次压缩A，将缩略图A生成我们需要的缩略图B。 5. 回收缩略图A（如果A和B的比率一样，就不回收A）。
 */
public class DecodeImageUtils {

	private static DecodeImageUtils decodeImageUtils;

	public static DecodeImageUtils get() {
		if (decodeImageUtils == null) {
			synchronized (DecodeImageUtils.class) {
				if (decodeImageUtils == null) {
					decodeImageUtils = new DecodeImageUtils();
				}
			}
		}
		return decodeImageUtils;
	}

	/**
	 * 因为压缩图片的时候要以2倍大小进行压缩，所以要 * 2
	 *
	 * @description 计算图片的压缩比率
	 *
	 * @param options
	 *            参数
	 * @param reqWidth
	 *            目标的宽度
	 * @param reqHeight
	 *            目标的高度
	 * @return
	 */
	private int calculateInSampleSize(BitmapFactory.Options options,
			int reqWidth, int reqHeight) {
		// 源图片的高度和宽度
		final int height = options.outHeight;
		final int width = options.outWidth;
		int inSampleSize = 1;
		if (height > reqHeight || width > reqWidth) {
			// 计算出实际宽高和目标宽高的比率
			final int halfHeight = height / 2;
			final int halfWidth = width / 2;
			while ((halfHeight / inSampleSize) > reqHeight
					&& (halfWidth / inSampleSize) > reqWidth) {
				inSampleSize *= 2;
			}
		}
		return inSampleSize;
	}

	/**
	 * @description 通过传入的bitmap，进行压缩，得到符合标准的bitmap
	 *
	 * @param src
	 * @param dstWidth
	 * @param dstHeight
	 * @return
	 */
	private Bitmap createScaleBitmap(Bitmap src, int dstWidth, int dstHeight,
			int inSampleSize) {
		// 如果是放大图片，filter决定是否平滑，如果是缩小图片，filter无影响，我们这里是缩小图片，所以直接设置为false
		Bitmap dst = Bitmap.createScaledBitmap(src, dstWidth, dstHeight, false);
		if (src != dst) { // 如果没有缩放，那么不回收
			src.recycle(); // 释放Bitmap的native像素数组
		}
		return dst;
	}

	/**
	 * @description 从Resources中加载图片
	 *
	 * @param res
	 * @param resId
	 * @param reqWidth
	 * @param reqHeight
	 * @return
	 */
	public Bitmap decodeSampledBitmapFromResource(Resources res, int resId,
			int reqWidth, int reqHeight) {
		// 第一次解析将inJustDecodeBounds设置为true，来获取图片大小
		final BitmapFactory.Options options = new BitmapFactory.Options();
		options.inJustDecodeBounds = true;
		BitmapFactory.decodeResource(res, resId, options);
		// 调用上面定义的方法计算inSampleSize值
		options.inSampleSize = calculateInSampleSize(options, reqWidth,
				reqHeight);
		// 使用获取到的inSampleSize值再次解析图片
		options.inJustDecodeBounds = false;
		return BitmapFactory.decodeResource(res, resId, options);
	}

	public Bitmap decodeBitmapFromResource(Resources res, int resId) {
		BitmapFactory.Options options = new BitmapFactory.Options();
		Bitmap src = BitmapFactory.decodeResource(res, resId, options); // 载入一个稍大的缩略图
		return createScaleBitmap(src, src.getWidth(), src.getWidth(),
				options.inSampleSize); // 通过得到的bitmap，进一步得到目标大小的缩略图
	}

	/**
	 * @description 从SD卡上加载图片
	 *
	 * @param pathName
	 * @param reqWidth
	 * @param reqHeight
	 * @return
	 */
	public Bitmap decodeSampledBitmapFromFile(String pathName, int reqWidth,
			int reqHeight) {
		final BitmapFactory.Options options = new BitmapFactory.Options();
		options.inJustDecodeBounds = true;
		BitmapFactory.decodeFile(pathName, options);
		options.inSampleSize = calculateInSampleSize(options, reqWidth,
				reqHeight);
		options.inJustDecodeBounds = false;
		Bitmap src = BitmapFactory.decodeFile(pathName, options);
		return createScaleBitmap(src, reqWidth, reqHeight, options.inSampleSize);
	}

	/**
	 * @description 从网络上加载图片
	 * @param reqWidth
	 * @param reqHeight
	 * @return
	 */
	public Bitmap decodeSampledBitmapFromInputStream(InputStream inputStream,
			int reqWidth, int reqHeight) {
		BitmapFactory.Options options = new BitmapFactory.Options();
		options.inJustDecodeBounds = true;
		Rect rect = new Rect(-1, -1, -1, -1);
		options.inSampleSize = calculateInSampleSize(options, reqWidth,
				reqHeight);
		options.inJustDecodeBounds = false;
		Bitmap src = BitmapFactory.decodeStream(inputStream, rect, options);
		return createScaleBitmap(src, reqWidth, reqHeight, options.inSampleSize);
	}

	public Bitmap convertToBitmap(String path, int w, int h) {
		BitmapFactory.Options opts = new BitmapFactory.Options();
		// 设置为ture只获取图片大小
		opts.inJustDecodeBounds = true;
		opts.inPreferredConfig = Bitmap.Config.ARGB_8888;
		// 返回为空
		BitmapFactory.decodeFile(path, opts);
		int width = opts.outWidth;
		int height = opts.outHeight;
		float scaleWidth = 0.f, scaleHeight = 0.f;
		if (width > w || height > h) {
			// 缩放
			scaleWidth = ((float) width) / w;
			scaleHeight = ((float) height) / h;
		}
		opts.inJustDecodeBounds = false;
		float scale = Math.max(scaleWidth, scaleHeight);
		opts.inSampleSize = (int) scale;
		WeakReference<Bitmap> weak = new WeakReference<Bitmap>(
				BitmapFactory.decodeFile(path, opts));
		return Bitmap.createScaledBitmap(weak.get(), w, h, true);
	}

	// drawable 转换成bitmap
	public Bitmap drawableToBitmap(Drawable drawable) {
		int width = drawable.getIntrinsicWidth();// 取drawable的长宽
		int height = drawable.getIntrinsicHeight();
		Bitmap.Config config = drawable.getOpacity() != PixelFormat.OPAQUE ? Bitmap.Config.ARGB_8888
				: Bitmap.Config.RGB_565;
		// 取drawable的颜色格式
		Bitmap bitmap = Bitmap.createBitmap(width, height, config);
		// 建立对应bitmap
		Canvas canvas = new Canvas(bitmap);
		// 建立对应bitmap的画布 drawable.setBounds(0, 0, width, height);
		drawable.draw(canvas);
		// 把drawable内容画到画布中
		return bitmap;
	}

	/**
	 * bitmap转为base64
	 * @param bitmap
	 * @return
	 */
	public String bitmapToBase64(Bitmap bitmap) {

		String result = null;
		ByteArrayOutputStream baos = null;
		try {
			if (bitmap != null) {
				baos = new ByteArrayOutputStream();
				bitmap.compress(Bitmap.CompressFormat.JPEG, 100, baos);
				baos.flush();
				baos.close();
				byte[] bitmapBytes = baos.toByteArray();
				result = Base64.encodeToString(bitmapBytes, Base64.DEFAULT);
			}
		} catch (IOException e) {
			e.printStackTrace();
		} finally {
			try {
				if (baos != null) {
					baos.flush();
					baos.close();
				}
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
		return result;
	}
	public static Bitmap returnBitmap(Context context, String url) {
		// TODO Auto-generated method stub
		Bitmap bitmap = null;
		HttpURLConnection con = null;
		try {
			// 建立网络连接
			URL imageURl = new URL(url);
			con = (HttpURLConnection) imageURl.openConnection();
			con.connect();
			InputStream is = con.getInputStream();
			bitmap = BitmapFactory.decodeStream(is);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} finally {
			con.disconnect();
		}

		if (bitmap == null) {
			bitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.em_default_avatar);
		}

		return bitmap;
	}
}